package com.chuangjiangx.member.manager.client.web.basic.service;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.Assert;

import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeUnit;

/**
 * 人脸识别的Redis服务类
 *
 * @author 马文韬
 * @version 1.0
 * @date: 2018/9/18
 */
@Service
public class FaceRecognitionRedisService {

    @Autowired
    private StringRedisTemplate redisTemplate;

    private List<Long> memberIds = new ArrayList<>();

    private String token = null;

    /**
     * 人脸识别过期时间 - 单位：分钟
     */
    private final int FACE_RECOGNITION_EXPIRE = 5;

    private final String PREFIX_REDIS_KEY = "faceRecognition";

    public void init(String token) {
        this.token = token;
    }

    /**
     * 添加识别出来的会员ID
     * @param memberId 会员ID
     */
    public void addRecogntionMemberId(long memberId) {
        addRecogntionMemberId(memberId, false);
    }

    /**
     * 添加识别出来的会员ID
     *
     * 完成添加后会设置过期时间为1分钟
     *
     * @param memberId 会员ID
     * @param isComplete 是否完成添加
     */
    public void addRecogntionMemberId(long memberId, boolean isComplete) {
        memberIds.add(memberId);

        if (isComplete) {
            complete();
        }
    }

    /**
     * 批量添加识别出来的会员ID
     * @param memberIds 会员列表集
     */
    public void addRecogntionMemberIds(Set<Long> memberIds) {
        addRecognitionMemberIds(memberIds, false);
    }

    /**
     * 批量添加识别出来的会员ID
     *
     * 完成添加后会设置过期时间为1分钟
     *
     * @param memberIds 会员列表集
     * @param isComplete 是否完成添加
     */
    public void addRecognitionMemberIds(Set<Long> memberIds, boolean isComplete) {
        for (Long memberId:
                memberIds) {
            this.memberIds.add(memberId);
        }

        if (isComplete) {
            complete();
        }
    }

    /**
     * 完成添加
     *
     * 完成添加后会设置过期时间
     */
    public void complete() {
        redisTemplate.opsForValue()
                .set(buildKey(), JSONArray.toJSONString(memberIds), FACE_RECOGNITION_EXPIRE, TimeUnit.MINUTES);
        memberIds.clear();
    }

    /**
     * 验证会员是否通过验证
     *
     * @param memberId 要验证的会员ID
     * @return 验证是否通过，true 通过
     */
    public boolean authenticatedMember(long memberId) {
        return authenticatedMember(memberId, false);
    }

    /**
     * 验证会员是否通过验证，并根据isClear去消除缓存的会员信息
     *
     * @param memberId 要验证的会员ID
     * @param isClear 是否清除验证信息，当值为 true 时，会清除验证信息，再次验证会失败
     * @return 验证是否通过，true 通过
     */
    public boolean authenticatedMember(long memberId, boolean isClear) {
        String key = buildKey();
        boolean isAuthenticated = false;
        List<Integer> memberIds = JSON.parseObject(redisTemplate.opsForValue().get(key), List.class);
        isAuthenticated = memberIds != null
                && memberIds.stream().anyMatch(id -> id != null && Long.valueOf(memberId).equals(id.longValue()));

        if(isClear) {
            clear();
        }

        return isAuthenticated;
    }

    public void clear() {
        String key = buildKey();
        redisTemplate.delete(key);
    }

    private String buildKey() {
        CheckToken();
        return PREFIX_REDIS_KEY + this.token;
    }

    private void CheckToken() {
        Assert.notNull(token, "使用前请初始化token的值，建议使用用户登录时生成的token");
    }

}
